package com.ruoyi.web.api;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.lang.Validator;
import cn.hutool.core.map.MapUtil;
import cn.hutool.core.util.IdUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.json.JSONObject;
import com.google.common.collect.Maps;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.*;
import com.ruoyi.common.utils.RedisUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.framework.web.service.SysLoginService;
import com.ruoyi.framework.web.service.SysRegisterService;
import com.ruoyi.service.CommonService;
import com.ruoyi.system.service.ISysDeptService;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.swing.text.StyledEditorKit;
import java.io.IOException;
import java.time.Duration;
import java.util.Map;
import java.util.Set;

import static com.ruoyi.common.constant.CacheConstants.APP_USER_INFO_MAP;
import static com.ruoyi.common.constant.CacheConstants.APP_USER_INFO_MAP_USER_ID;

/**
 * @author liutao
 * @version 1.0
 * @description: TODO
 * @date 2024/3/8 18:07
 */
@RestController
@RequestMapping("/api")
public class LoginApi {
    @Resource
    private SysLoginService loginService;
    @Resource
    private ISysDeptService deptService;

    @Resource
    private CommonService commonService;
    @Resource
    private SysRegisterService registerService;

    @GetMapping("/captchaImage")
    public R<Map<String, Object>> getCode(HttpServletResponse response) throws IOException {
        Map<String, Object> result = commonService.getCode();
        return R.ok(result);
    }

    /**
     * app登录方法
     *
     * @param loginBody 登录信息
     * @return 结果
     */
    @PostMapping("/login")
    public R<Map<String, Object>> login(@RequestBody LoginBody loginBody) {
        Map<String, Object> result = Maps.newHashMap();
        boolean isValid = Validator.isMobile(loginBody.getUsername());
        if (!isValid) {
            return R.fail("登录手机号码错误");
        }
        // 生成令牌
        String token = loginService.login(loginBody.getUsername(), loginBody.getPassword(), loginBody.getCode(),
                loginBody.getUuid(), Constants.LOGIN_TYPE_APP);
        result.put(Constants.TOKEN, token);
        return R.ok(result);
    }

    /**
     * APP获取用户信息
     *
     * @return 用户信息
     */
    @GetMapping("/getInfo")
    public R<AppLoginUser> getInfo() {
        LoginUser user = SecurityUtils.getLoginUser();
        String cacheKey = StrUtil.format(APP_USER_INFO_MAP_USER_ID, user.getUserId());
        AppLoginUser appLoginUser = RedisUtils.getCacheMapValue(APP_USER_INFO_MAP, cacheKey);
        if (appLoginUser == null) {
            appLoginUser = new AppLoginUser();
            BeanUtil.copyProperties(user.getUser(), appLoginUser);
            SysDept dept = deptService.getById(user.getDeptId());
            if (dept != null) {
                appLoginUser.setDeptName(dept.getDeptName());
            }
            RedisUtils.setCacheMapValue(APP_USER_INFO_MAP, cacheKey, appLoginUser);
        }

        return R.ok(appLoginUser);
    }

    @PostMapping("/register")
    public R<Boolean> register(@RequestBody @Validated AppRegisterBody registerBody) {
        Boolean flag = registerService.appRegister(registerBody);
        if (Boolean.TRUE.equals(flag)) {
            return R.ok();
        } else {
            return R.fail();
        }

    }

    @PostMapping("/checkCode")
    public R<Map<String, Object>> checkCode(@RequestBody JSONObject jsonObject) {
        String code = jsonObject.getStr("code");
        if (StrUtil.isEmpty(code)) {
            return R.fail("验证码不能为空");
        }
        String phone = jsonObject.getStr("phone");
        if (StrUtil.isEmpty(phone)) {
            return R.fail("手机号码不能为空");
        }
        Long userId = loginService.retrievePassword(phone, code);
        String uid = IdUtil.getSnowflakeNextIdStr();
        Map<String, Object> result = Maps.newHashMap();
        result.put("userId", userId);
        result.put("uid", uid);
        RedisUtils.setCacheObject(StrUtil.format(CacheConstants.RETRIEVE_PASSWORD_CODE_KEY, userId), uid, Duration.ofMinutes(3));
        return R.ok(result);
    }
}
